package com.atguigu.yygh.Controller;

import com.atguigu.yygh.common.MD5;
import com.atguigu.yygh.common.result.R;
import com.atguigu.yygh.common.result.Result;
import com.atguigu.yygh.model.hosp.HospitalSet;
import com.atguigu.yygh.service.HospitalSetService;
import com.atguigu.yygh.vo.hosp.HospitalSetQueryVo;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.fasterxml.jackson.annotation.JsonTypeInfo;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.*;

import java.util.*;

//@CrossOrigin
@Api
@RestController
@RequestMapping("/admin/hosp/hospitalSet")
public class HospitalSetController {

    //注入service层
    @Autowired
    private HospitalSetService hospitalSetService;


    /**
     * 1.查询医院设置表里面的所有的信息
     */
    @ApiOperation("查询医院设置表里面的所有的信息")
    @GetMapping("findAll")
    public R findAllHospitalSet() {
        //调用Service层的方法
        List<HospitalSet> list = hospitalSetService.list();
        Map map = new HashMap<>();
        map.put("list", list);
        /* Result<List<HospitalSet>> result = Result.ok(list);*/
        return R.ok().data(map);
    }

    /**
     * 2.删除指定id的医院设置表里面的信息
     * 使用的是逻辑删除
     */
    @DeleteMapping("{id}")
    public R deleteById(@PathVariable("id") Long id) {
        //调用Service层的方法
        boolean flag = hospitalSetService.removeById(id);
        if (flag) {
            return R.ok();
        } else {
            return R.error();
        }
    }

    /**
     * 3.条件查询带分页
     * (1)参数：当前页和每页的记录数
     * (2)封装条件的vo对象【将查询的条件封装到vo对象】接收前端的查询条件
     */
    @PostMapping("findPage/{current}/{limit}")
    public R findPageHospSet(@PathVariable("current") Long current,
                                  @PathVariable("limit") Long limit,
                                  //get请求是在URL中拼接参数
                                  //RequestBody前端使用JSON传输数据，请求的方式必须为POST【使用Response注解传输JSON数据】
                                  //将查询条件变为JSON格式
                                  //false不需要传递这个参数
                                  @RequestBody(required = false) HospitalSetQueryVo hospitalSetQueryVo) {
        //(1)创建page对象，传递当前页，每页的记录数
        Page<HospitalSet> page = new Page<>(current, limit);

        //(2)利用wrapper构造条件
        QueryWrapper<HospitalSet> wrapper = new QueryWrapper<>();

        //(3)对条件值进行健壮性的判断，如果值为空则不需要进行判断，如果值不为空则不需要进行判断【防止空指针异常】
        String hosname = hospitalSetQueryVo.getHosname();//医院的名称
        String hoscode = hospitalSetQueryVo.getHoscode();//医院的编号

        if (!StringUtils.isEmpty(hosname)) {//import org.springframework.util.StringUtils
            //必须是不等于空的情况下才拼接条件   key=""     key=null
            //模糊查询医院的名称[表中的列名]
            wrapper.like("hosname", hospitalSetQueryVo.getHosname());
        }
        if (!StringUtils.isEmpty(hoscode)) {
            //精确匹配医院的编号
            wrapper.eq("hoscode", hospitalSetQueryVo.getHoscode());
        }

        //调用查询方法
        //(4)调用Service层的方法实现分页查询【两个差参数，第一个是page对象，第二个分页的条件】
        Page<HospitalSet> pageHospitalSet = hospitalSetService.page(page, wrapper);


        //4、返回值解析
        List<HospitalSet> records =pageHospitalSet.getRecords();//当前页数据集合
        long total = pageHospitalSet.getTotal();//总记录数（前端会根据total进行显示分页控件）


        //5、封装返回值
        return R.ok().data("rows", records).data("total", total);
    }

    /**
     * 4.添加医院设置
     * 添加医院设置的信息
     * 信息使用对象进行传递
     * 签名秘钥【接头的暗号】
     * 状态
     * 需要单独继续设置
     */
    @PostMapping("saveHospitalSet")
    public R saveHospitalSet(@RequestBody HospitalSet hospitalSet) {
        //设置状态 1 使用 0 不能使用
        hospitalSet.setStatus(1);

        //设置签名密钥
        Random random = new Random();//生成随机数

        //设置MD5加密【和医院的接口对接的时候呀进行使用】
        hospitalSet.setSignKey(MD5.encrypt(System.currentTimeMillis() + "" + random.nextInt(1000)));

        //调用service
        boolean save = hospitalSetService.save(hospitalSet);
        if (save) {
            return R.ok();
        } else {
            return R.error();
        }
    }

    /**
     * 5.根据id获取医院的设置
     */
    @GetMapping("getHospSet/{id}")
    public R getHospSet(@PathVariable Long id) {
        HospitalSet hospitalSet = hospitalSetService.getById(id);
        return R.ok().data("item", hospitalSet);
    }

    /**
     * 6.修改医院设置
     * <p>
     * requestbody注解使用JSON接收前端的参数
     * 使用对象接收参数
     * 意思是使用JSON对象接参数？？？？？？
     */
    @PostMapping("updateHospitalSet")
    public R updateHospitalSet(@RequestBody HospitalSet hospitalSet) {
        boolean flag = hospitalSetService.updateById(hospitalSet);
        if (flag) {
            return R.ok();
        } else {
            return R.error();
        }
    }

    /**
     * 7.批量删除医院设置
     */
    @DeleteMapping("batchRemove")
    public R batchRemoveHospitalSet(@RequestBody List<Long> idList) {
        hospitalSetService.removeByIds(idList);
        return R.ok();
    }

    /**
     * 8.医院设置锁定和解锁的接口
     * 医院的接口锁定，平台就不能与其对接
     * status是1表示解锁
     * status是0表示锁定
     * 说白了就是一个修改的操作
     * （1）传递对应的id和状态码
     * （2）对状态码进行判断
     *
     *
     * 直接调用修改的方法，不参与修改的属性其他值为null，不会覆盖之前的值
     * 先通过id获取对象，再进行修改的，不参与修改的属性【原先的createtime】会覆盖【自动改变的createtime】
     */

    @PutMapping("lockHospitalSet/{id}/{status}")
    public R lockHospitalSet(@PathVariable("id") Long id, @PathVariable("status") Integer status) {

        //不管是从哪获得的数据，在使用之前一定要健壮性判断
        if (status == 1 || status == 0) {
            //根据id查询出医院设置的信息[对应id的对象]
            HospitalSet hospitalSet = hospitalSetService.getById(id);
            if (hospitalSet == null) {
                return R.error().message("该医院不存在");
            } else {
                hospitalSet.setStatus(status);
                hospitalSet.setUpdateTime(new Date());//最后的更新时间
                hospitalSetService.updateById(hospitalSet);//TODO 会将更新时间覆盖，拿到的是旧对象的属性
                return R.ok().message(status == 0 ? "锁定成功" : "解锁成功");
            }
        }
        return R.error().message("status只能为0或1");
    }

    /**
     * 8.发送签名秘钥
     * 医院的接口与平台的接口对接双方需要约定好一个密钥
     * 在做添加医院的设置的时候，利用MD5生成了一个密钥
     * 所以需要将密钥发送给医院那边的接口
     * 医院那边的接口对这个密钥进行配置才能实现对接
     * 【发送过程其实即使发送短信，验证码的一个过程】
     */

    @PutMapping("sendKey/{id}")
    public Result sendKey(@PathVariable("id") Long id){

        //根据id查询出医院设置的信息[对应id的对象]
        HospitalSet hospitalSet = hospitalSetService.getById(id);

        //获取到医院的对应的信息
        String signKey = hospitalSet.getSignKey();
        String hoscode = hospitalSet.getHoscode();

        //调用方法
        hospitalSetService.updateById(hospitalSet);
        //TODO  发送短信

        return Result.ok();
    }
}
